package com.qinglei.recoup.system.manager;

import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.qinglei.recoup.common.domain.CommonConstant;
import com.qinglei.recoup.common.domain.RadarMessage;
import com.qinglei.recoup.common.domain.RadarUserDataDTO;
import com.qinglei.recoup.common.exception.RedisConnectException;
import com.qinglei.recoup.common.service.RedisService;
import com.qinglei.recoup.system.dao.BedHealthStateMapper;
import com.qinglei.recoup.system.dao.BedMapper;
import com.qinglei.recoup.system.domain.Bed;
import com.qinglei.recoup.system.domain.BedHealthState;
import com.qinglei.recoup.system.enums.EventEnum;
import com.qinglei.recoup.system.service.BedHealthBreathDailyDataService;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Component;
import org.springframework.transaction.annotation.Transactional;

import java.util.List;

/**
 * 呼吸心跳报警，封装3.0 协议呼吸、心跳报警
 */
@Component
@Slf4j
public class BreathHeartAlarmV3 {

    @Autowired
    private BedMapper bedMapper;

    @Autowired
    private BedHealthStateMapper bedHealthStateMapper;

    @Autowired
    private BedHealthBreathDailyDataService bedHealthBreathDailyDataService;

    @Autowired
    private RedisService redisService;

    @Value("${Health.v3BreathLow}")
    private Integer v3BreathLow;

    @Value("${Health.v3BreathHight}")
    private Integer v3BreathHight;

    @Value("${Health.v3HeartLow}")
    private Integer v3HeartLow;

    @Value("${Health.v3HearthHight}")
    private Integer v3HearthHight;

    @Value("${Health.v3BreathTimeSsecond}")
    private Integer v3BreathTimeSsecond;

    @Value("${Health.v3HeartTimeSsecond}")
    private Integer v3HeartTimeSsecond;


    /**
     * 记录呼吸、心跳异常事件
     *
     * @param message
     */
    @Transactional
    public void updateBreathStatus(RadarMessage message)   {

        RadarUserDataDTO data = (RadarUserDataDTO) message.getData();
        // S2状态为离床 并且 S1状态为非配合时 不产生报警 TODO 取消报警有问题
        if (data.getS2() == 0 || data.getS1() != 13) {
            return;
        }
        Bed bed = bedMapper.selectBySn(message.getSn());

        if (bed == null) {
            log.debug("procRadarData not bind bed sn: {}", message.getSn());
            return;
        }

        if(bed.getStatus()==2 ||bed.getSubStatus()==1){ //离床 或 报警情况下不产生报警
            return;
        }

        Integer breathBpm = data.getBreathBpm();
        Integer heartBpm  = data.getHeartBpm();
        String bedId = String.valueOf(bed.getId());

        QueryWrapper queryWrapper = new QueryWrapper();
        queryWrapper.eq("bed_id",bedId);
        List<BedHealthState> bedHealthStates =  bedHealthStateMapper.selectList(queryWrapper);
        boolean isHeaythAlrem = (bedHealthStates!=null && bedHealthStates.size()>0);
        try {

            //处理呼吸BPM
            if(breathBpm >= v3BreathHight && !isHeaythAlrem) {  //30
                //呼吸过快
                removeKey(CommonConstant.BREATH_BPM_LOW_TIME_START, bedId);
                addKey(CommonConstant.BREATH_BPM_HIGHT_TIME_START, bedId);
            } else if(breathBpm>v3BreathLow && breathBpm <v3BreathHight){  //6  30
                processingDataBreath(bed);
            }if(breathBpm<=v3BreathLow && !isHeaythAlrem){  //6
                //呼吸过慢
                removeKey(CommonConstant.BREATH_BPM_HIGHT_TIME_START, bedId);
                addKey(CommonConstant.BREATH_BPM_LOW_TIME_START, bedId);


            }

            //处理心跳BPM
            if(heartBpm >= v3HearthHight && !isHeaythAlrem){ //心跳过快  //90
                removeKey(CommonConstant.HEART_BPM_LOW_TIME_START, bedId);
                addKey(CommonConstant.HEART_BPM_HIGHT_TIME_START, bedId);
            } else if(heartBpm>v3HeartLow && heartBpm <v3HearthHight){ //心跳正常  // 45  90
                processingDataHeaart(bed);
            }if(heartBpm <= v3HeartLow && !isHeaythAlrem){  //心跳过慢
                removeKey(CommonConstant.HEART_BPM_HIGHT_TIME_START, bedId);
                addKey(CommonConstant.HEART_BPM_LOW_TIME_START, bedId);

            }

        }catch (RedisConnectException ex){
            log.debug("RedisConnectException : {}",  ex.fillInStackTrace());
            return;
        }

    }

    /**
     * 新增键值对
     * @param type
     * @param bedId
     * @throws RedisConnectException
     */
    private void addKey(String type, String bedId) throws RedisConnectException {
        if (redisService.get(type+"-"+bedId) == null) {
            redisService.set(type+"-"+bedId,"1");
        }else {

            redisService.incr(type+"-"+bedId);
            Integer alarmNumber = Integer.valueOf(redisService.get(type+"-"+bedId));

            if(type.equals(CommonConstant.BREATH_BPM_HIGHT_TIME_START)){
                if(alarmNumber==v3BreathTimeSsecond+1){
                    bedHealthBreathDailyDataService.breathBpmHight(bedId);
                }
            }else if(type.equals(CommonConstant.BREATH_BPM_LOW_TIME_START)){
                if(alarmNumber==v3BreathTimeSsecond+1){
                    bedHealthBreathDailyDataService.breathBpmLow(bedId);
                }
            }else if(type.equals(CommonConstant.HEART_BPM_HIGHT_TIME_START)){
                if(alarmNumber==v3HeartTimeSsecond+1){
                    bedHealthBreathDailyDataService.heartBpmHight(bedId);
                }
            }else if(type.equals(CommonConstant.HEART_BPM_LOW_TIME_START)){
                if(alarmNumber==v3HeartTimeSsecond+1){
                    bedHealthBreathDailyDataService.heartBpmLow(bedId);
                }
            }
        }
    }

    /**
     * 删除键值对
     * @param type
     * @param bedId
     * @throws RedisConnectException
     */
    private void removeKey(String type,String bedId) throws RedisConnectException {
        if (redisService.get(type+"-"+bedId) != null) {
            redisService.del(type+"-"+bedId);
        }


    }


    public void  processingDataBreath(Bed bed) throws RedisConnectException {
        String bedId = String.valueOf(bed.getId());
        //正常
        String breathBpmNomalFlag =redisService.get(CommonConstant.BREATH_BPM_NOMAL+bedId);
        removeKey(CommonConstant.BREATH_BPM_HIGHT_TIME_START, bedId);
        removeKey(CommonConstant.BREATH_BPM_LOW_TIME_START, bedId);
        if(breathBpmNomalFlag==null){
            redisService.set(CommonConstant.BREATH_BPM_NOMAL+bedId,CommonConstant.BREATH_BPM_NOMAL);
            //消除报警
            QueryWrapper queryWrapperLow = new QueryWrapper();
            queryWrapperLow.eq("bed_id",bed.getId());
            bedHealthStateMapper.delete(queryWrapperLow);
            bedHealthBreathDailyDataService.processingDataRecovery(bed,BedHealthState.SUB_STATUS_BREATH_NORMAL, EventEnum.ALARM_BREATH_BPM_NORMAL.getCode(),EventEnum.ALARM_BREATH_BPM_NORMAL.getContent());
        }
    }

    public void  processingDataHeaart(Bed bed) throws RedisConnectException {
        String bedId = String.valueOf(bed.getId());
        String heattBpmNomalFlag =redisService.get(CommonConstant.HEART_BPM_NOMAL+bedId);
        removeKey(CommonConstant.HEART_BPM_LOW_TIME_START, bedId);
        removeKey(CommonConstant.HEART_BPM_HIGHT_TIME_START, bedId);
        if(heattBpmNomalFlag==null){
            QueryWrapper queryWrapperHight = new QueryWrapper();
            queryWrapperHight.eq("bed_id",bed.getId());
            queryWrapperHight.eq("type",BedHealthState.SUB_STATUS_HEART_HIGHT);
            bedHealthStateMapper.delete(queryWrapperHight);

            QueryWrapper queryWrapperLow = new QueryWrapper();
            queryWrapperHight.eq("bed_id",bed.getId());
            queryWrapperHight.eq("type",BedHealthState.SUB_STATUS_HEART_LOW);
            bedHealthStateMapper.delete(queryWrapperLow);

            redisService.set(CommonConstant.HEART_BPM_NOMAL+bedId,CommonConstant.HEART_BPM_NOMAL);
            bedHealthBreathDailyDataService.processingDataRecovery(bed,BedHealthState.SUB_STATUS_HEART_NORMAL,EventEnum.ALARM_HEART_BPM_NORMAL.getCode(),EventEnum.ALARM_HEART_BPM_NORMAL.getContent());
        }
    }

    public void clearAlearm(Integer  bedId){
        String bedIdstr = String.valueOf(bedId);
        try {
            removeKey(CommonConstant.BREATH_BPM_HIGHT_TIME_START, bedIdstr);
            removeKey(CommonConstant.BREATH_BPM_LOW_TIME_START, bedIdstr);
            removeKey(CommonConstant.HEART_BPM_LOW_TIME_START, bedIdstr);
            removeKey(CommonConstant.HEART_BPM_HIGHT_TIME_START, bedIdstr);
            redisService.set(CommonConstant.BREATH_BPM_NOMAL+bedId,CommonConstant.BREATH_BPM_NOMAL);
            redisService.set(CommonConstant.HEART_BPM_NOMAL+bedId,CommonConstant.HEART_BPM_NOMAL);
        }catch (RedisConnectException e){
            e.fillInStackTrace();
        }
        QueryWrapper queryWrapperHight = new QueryWrapper();
        queryWrapperHight.eq("bed_id",bedId);
        bedHealthStateMapper.delete(queryWrapperHight);
    }

}
